import { FC, ReactElement, useCallback, useEffect, useState } from "react";
import styled from "styled-components";
import {
  BlogDetail,
  getBlogById,
  queryBlogThumbsState,
  thumbsBlog,
  cancelThumbs,
  transformThumbs,
} from "../../api/blogApi";
import MarkDown from "../../components/MD/MarkDown";
import { FlexDiv, ThemeFlexDiv } from "../../components/BUI";
import { ThemeText } from "../../components/BUI/View/ThemeView";
import {
  MarkDownText,
  BlogTypeTag,
  OptionalItem,
  fadeIn,
  ContentCss,
  ContentWidth,
} from "../../components/commentStyled";
import { BrowseIcon, CommentIcon } from "../../components/BUI/Icon";
import SEO from "../../layout/SEO";
import { useAuth } from "../../context/AuthProvide";
import { userProfileRef } from "../../layout/UserProfile";
import Thumbs from "../../components/Blog/Thumbs";
import Comment from "../../components/Blog/Comment";
import { useRouter } from "next/router";

interface IProps {
  readonly blog: BlogDetail;
}

export type ThumbsState = "" | "UP" | "DOWN";

const Blog: FC<IProps> = ({ blog }): ReactElement => {
  const { auth } = useAuth();
  const { push } = useRouter();
  const [focusUpdate, setFocusUpdate] = useState(0); //用于强制更新
  const [thumbsUpCount, setThumbsUpCount] = useState(blog.thumbsUp);
  const [thumbsDownCount, setThumbsDownCount] = useState(blog.thumbsDown);
  const [thumbsState, setThumbsState] = useState<ThumbsState>(""); // 点赞状态
  const [thumbsLoading, setThumbsLoading] = useState<ThumbsState>(""); // 点赞中状态

  useEffect(() => {
    if (blog.content.slice(0, 7) === "@[toc]\n") {
      setFocusUpdate(Math.random());
    }
  }, [blog.content]);

  useEffect(() => {
    if (!auth._id) return;
    // 查询当前用户的点赞列表中是否有这篇博客
    queryBlogThumbsState({ userId: auth._id, blogId: blog._id }).then(res => {
      console.log("queryBlogThumbsState:", res);
      if (res.data) {
        setThumbsState(res.data);
      }
    });
  }, [auth._id, blog._id]);

  const handleThumbs = useCallback(
    (type: ThumbsState) => () => {
      //点赞需要登陆账户 移动端不支持 ?. 语法
      if (!auth.username)
        return userProfileRef.current && userProfileRef.current.open();
      if (thumbsLoading) return;
      const params = { blogId: blog._id, userId: auth._id };
      setThumbsLoading(type);
      //收回点赞  当前有选中按钮
      if (thumbsState) {
        //当前点击是选中的 取消点赞/踩
        if (type === thumbsState) {
          cancelThumbs({ ...params, type }).then(res => {
            console.log("cancelThumbs:", res);
            if (res && res.data) {
              setThumbsState("");
              setThumbsUpCount(count => count - 1);
              setThumbsLoading("");
            }
          });
        } else {
          //当前点击不是之前选中的 取消点赞/踩 增加另一个
          transformThumbs({ ...params, from: thumbsState, to: type }).then(
            res => {
              console.log("cancelThumbs:", res);
              if (res && res.data) {
                setThumbsState(type);
                setThumbsLoading("");
                setThumbsUpCount(count => count + (type === "UP" ? 1 : -1));
                setThumbsDownCount(count => count + (type === "DOWN" ? 1 : -1));
              }
            }
          );
        }
      }
      //点赞
      else {
        thumbsBlog(params, type).then(res => {
          console.log(res);
          if (res && res.data) {
            setThumbsState(type);
            setThumbsLoading("");
            type === "UP"
              ? setThumbsUpCount(count => count + 1)
              : setThumbsDownCount(count => count + 1);
          }
        });
      }
    },
    [auth._id, auth.username, blog._id, thumbsLoading, thumbsState]
  );

  if (!blog) return <Container>请求出错！</Container>;

  return (
    <Container>
      <SEO title={blog.title} description={blog.content.substr(0, 20)} />
      <Content column>
        <FlexDiv items="center" justify="center" space="2px">
          <h2>{blog.title}</h2>
          <BlogTypeTag>{blog.type}</BlogTypeTag>
          <OptionalItem space="2px">
            <BrowseIcon />
            <span>{blog.browseCount}</span>
          </OptionalItem>
          <OptionalItem
            space="2px"
            onClick={() => push(`/user/${blog.sender[0]?._id}`)}
          >
            <span>作者</span>
            <span>{blog.sender[0]?.username}</span>
          </OptionalItem>
        </FlexDiv>
        <MarkDown syncScroll={false} content={blog.content} />
        <FlexDiv justify="flex-end">
          <OptionalItem space="2px">
            <CommentIcon />
            <span>{blog.commentCount}</span>
          </OptionalItem>
          <Thumbs
            thumbsState={thumbsState}
            handleThumbs={handleThumbs}
            thumbsUp={thumbsUpCount}
            thumbsDown={thumbsDownCount}
            thumbsLoading={thumbsLoading}
          />
        </FlexDiv>
      </Content>
      <Comment senderId={auth._id} blogId={blog._id} />
    </Container>
  );
};

export default Blog;

export const getServerSideProps = async ({ query: { id } }: any) => {
  const { data = "" } = await getBlogById(id);

  return {
    props: {
      blog: data,
    },
  };
};

const Container = styled(FlexDiv).attrs({
  column: true,
})`
  animation: ${fadeIn} 0.3s linear;
  min-height: calc(100vh - var(--nav-height));
  ${ContentWidth};
  padding: 1rem;
  margin: auto;
`;

const Content = styled(ThemeFlexDiv)`
  ${ThemeText};
  ${ContentCss};
  ${MarkDownText};
  width: 100%;
  padding: 1rem;
  margin: 0;
  margin-top: 1rem;
`;
